package com.example.sort.sort;



import com.example.sort.constant.SortConstant;
import com.example.sort.entity.RectangleInfo;
import com.example.sort.service.impl.SortServiceImpl;
import io.jenetics.Chromosome;
import io.jenetics.Genotype;
import io.jenetics.IntegerChromosome;
import io.jenetics.IntegerGene;
import io.jenetics.util.IntRange;
import lombok.Data;
import mckaylib.ga.engine.converters.DefaultSolutionConverter;
import mckaylib.ga.engine.core.AbstractSolution;
import mckaylib.ga.engine.core.DefaultSolution;
import mckaylib.ga.engine.core.EvolvingSolutionInfo;

import java.util.ArrayList;
import java.util.List;

public class Demo1SolutionConverter extends DefaultSolutionConverter {
    public List<RectangleInfo> initList;

    public List<RectangleInfo> finalList;

    public void sortInit() {
        initList = SortServiceImpl.initList;
        finalList =new ArrayList<>();
    }


    @Override
    public AbstractSolution convert2Solution(EvolvingSolutionInfo solutionInfo) {
        Demo1Solution solution = new Demo1Solution();
        solution.setFitnessValues(solutionInfo.getFitnessValues());

        //这个是获取基因架
        Genotype<IntegerGene> geneMap = solutionInfo.getMap();

        //获取默认的也就是第一个基因条
        Chromosome<IntegerGene> chromosome = geneMap.getChromosome();

        //开始业务解码
        for (int idx = 0; idx < chromosome.length(); idx++) {
            IntegerGene integerGene = chromosome.getGene(idx);
            if (!solution.getSelectedIds().contains(integerGene.intValue())) {
                solution.getSelectedIds().add(integerGene.intValue());
            } else {
                Boolean add = true;
                Integer initValue = integerGene.intValue();
                while (add) {
                    if (!solution.getSelectedIds().contains(initValue)) {
                        solution.getSelectedIds().add(initValue);
                        add = false;
                    } else {
                        if (initValue == 0) {
                            initValue = chromosome.length() - 1;
                        } else {
                            initValue -= 1;
                        }
                    }
                }
            }
        }
        return solution;
    }

    /**
     * 这个是唯一一个DefaultSolutionConverter种的抽象方法，必须实现，用来定义基因序列的组成
     *
     * @return
     */
    @Override
    public Genotype<IntegerGene> loadGenotype(Integer size) {
        Genotype<IntegerGene> genotype = Genotype.of(

                IntegerChromosome.of(0, size - 1, IntRange.of(size))
        );
        return genotype;
    }

    /**
     * 这个是适应度函数定义，要注意入参和出参，这2个是固定的
     *
     * @param solution
     * @return
     */
    public double getRate(AbstractSolution solution) {
        Demo1Solution s = (Demo1Solution) solution;
        //初始赋值
        sortInit();
        //用基因顺序取出初始数据到
        getNewSort(s.getSelectedIds());
        SortServiceImpl sortService=new SortServiceImpl();
        sortService.sortList(this.finalList);
        Double areaUsing = this.finalList.stream().filter(x -> x.getIsOrder().equals(true)).mapToDouble(x->(x.getWidth()*x.getLength())).sum();
        //排序占比
        Double result = (areaUsing * 100 / (SortConstant.length*SortConstant.width));
        return result;

    }



    public void getNewSort(List<Integer> listOrder) {
        for (int i = 0; i < this.initList.size(); i++) {
            this.finalList.add(new RectangleInfo(this.initList.get(listOrder.get(i)).getLength(),this.initList.get(listOrder.get(i)).getWidth()));
        }
    }

    /**
     * 这个是业务解码后存放的class，很好理解
     */
    @Data
    public class Demo1Solution extends DefaultSolution {

        private List<Integer> selectedIds = new ArrayList<>();

        @Override
        public String toString() {
            StringBuilder stringBuilder = new StringBuilder();

            for (int id : selectedIds) {
                stringBuilder.append(id);
                stringBuilder.append(", ");
            }

            return stringBuilder.toString();
        }
    }
}
